package com.springboot.service.impl;

import com.springboot.constant.HealthRecordExecl;
import com.springboot.dto.HealthRecordDTO;
import com.springboot.entity.HealthRecord;
import com.springboot.entity.WxUser;
import com.springboot.enums.WxUserStatus;
import com.springboot.repository.HealthRecordRepositiry;
import com.springboot.repository.WxUserRepository;
import com.springboot.service.HealthRecordService;
import com.springboot.utils.ExeclUtil;
import com.springboot.vo.AdminHealthRecordListVO;
import com.springboot.vo.HealthRecordListVO;
import com.springboot.vo.PageVO;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.stereotype.Service;

import javax.persistence.criteria.Predicate;
import javax.transaction.Transactional;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @author: lzh
 */
@Service
@Transactional
public class HealthRecordServiceImpl implements HealthRecordService {

    @Autowired
    HealthRecordRepositiry healthRecordRepositiry;

    @Autowired
    WxUserRepository wxUserRepository;

    /**
     * @descrition:  扫码后记录用户
     * @param healthRecordDTO :
     * @return : void
     */
    @Override
    public void addHealthRecord(HealthRecordDTO healthRecordDTO) {
        HealthRecord healthRecord = new HealthRecord();
        WxUser wxUser = wxUserRepository.getOne(healthRecordDTO.getWxUserId());
        if(healthRecordDTO.getTemperature() < 37.2) {
            wxUser.setStatus(WxUserStatus.HEALTHY.getMsg());
        } else if(healthRecordDTO.getTemperature() > 37.5) {
            wxUser.setStatus(WxUserStatus.SICK.getMsg());
        } else {
            Page<HealthRecord> page = healthRecordRepositiry.findAll((root, criteriaQuery, criteriaBuilder) -> {
                Predicate wxUserId = criteriaBuilder.equal(root.get("wxUserId"), wxUser.getId());
                criteriaQuery.orderBy(criteriaBuilder.desc(root.get("time")));
                return criteriaBuilder.and(wxUserId);
            }, PageRequest.of(0, 2));
            long size =  page.getContent().stream()
                    .filter(h -> (h.getTemperature() > 37.2 && h.getTemperature() <= 37.5))
                    .count();
            if(size == 2) {
                wxUser.setStatus(WxUserStatus.ATTENTION.getMsg());
            } else {
                wxUser.setStatus(WxUserStatus.HEALTHY.getMsg());
            }
        }
        wxUserRepository.save(wxUser);
        BeanUtils.copyProperties(healthRecordDTO, healthRecord);
        healthRecord.setTime(new Date());
        healthRecordRepositiry.save(healthRecord);
    }

    @Override
    public PageVO getHealthRecordList(Integer pageNum, Integer pageSize
            , String keywords, Date time) {
        Page<HealthRecord> healthRecordPage = healthRecordRepositiry.findAll((root, criteriaQuery, criteriaBuilder) -> {
            List<Predicate> predicates = new ArrayList<>();
            //按关键字查询
            if (keywords != null && keywords.length() != 0) {
                predicates.add(criteriaBuilder.like(root.get("name"), "%" + keywords + "%"));
            }
            //按时间查询
            if (time != null) {
                Calendar calendar = Calendar.getInstance();
                calendar.setTime(time);
                calendar.add(Calendar.DAY_OF_MONTH, 1);
                predicates.add(criteriaBuilder.between(root.get("time"), time, calendar.getTime()));
            }
            //按时间排序
            criteriaQuery.orderBy(criteriaBuilder.desc(root.get("time")));
            return criteriaBuilder.and(predicates.toArray(new Predicate[predicates.size()]));
        }, PageRequest.of(pageNum - 1, pageSize));
        PageVO pageVO = PageVO.convert(healthRecordPage);
        //封装数据
        List<HealthRecordListVO> healthRecordListVOList = healthRecordPage.getContent().stream().map(healthRecord -> {
            HealthRecordListVO healthRecordListVO = new HealthRecordListVO();
            BeanUtils.copyProperties(healthRecord, healthRecordListVO);
            healthRecordListVO.setAvatarUrl(healthRecord.getWxUser().getAvatarUrl());
            healthRecordListVO.setName(healthRecord.getWxUser().getName());
            healthRecordListVO.setIsRegident(healthRecord.getWxUser().getIsRegident());
            return healthRecordListVO;
        }).collect(Collectors.toList());
        pageVO.setContent(healthRecordListVOList);
        return pageVO;
    }

    @Override
    public PageVO adminGetHealthRecordList(Integer pageNum, Integer pageSize, String keywords, Date begin, Date end) {
        Page<HealthRecord> healthRecordPage = healthRecordRepositiry.findAll((root, criteriaQuery, criteriaBuilder) -> {
            List<Predicate> predicates = new ArrayList<>();
            //按关键字查询
            if (keywords != null && keywords.length() != 0) {
                predicates.add(criteriaBuilder.like(root.get("wxUser").get("name"), "%" + keywords + "%"));
            }
            //按时间查询
            if(begin != null && end != null) {
                predicates.add(criteriaBuilder.between(root.get("time"), begin, end));
            } else if (begin != null) {
                predicates.add(criteriaBuilder.greaterThanOrEqualTo(root.get("time"), begin));
            } else if(end != null) {
                predicates.add(criteriaBuilder.lessThanOrEqualTo(root.get("time"), end));
            }
            //按时间排序
            criteriaQuery.orderBy(criteriaBuilder.desc(root.get("time")));
            return criteriaBuilder.and(predicates.toArray(new Predicate[predicates.size()]));
        }, PageRequest.of(pageNum - 1, pageSize));
        PageVO pageVO = PageVO.convert(healthRecordPage);
        List<AdminHealthRecordListVO> healthRecordListVOList = healthRecordPage.getContent().stream().map(healthRecord -> {
            AdminHealthRecordListVO healthRecordListVO = new AdminHealthRecordListVO();
            BeanUtils.copyProperties(healthRecord, healthRecordListVO);
            WxUser wxUser = healthRecord.getWxUser();
            healthRecordListVO.setName(wxUser.getName());
            healthRecordListVO.setIsRegident(wxUser.getIsRegident());
            healthRecordListVO.setGender(wxUser.getGender());
            healthRecordListVO.setStatus(wxUser.getStatus());
            healthRecordListVO.setRoomNumber(wxUser.getRoomNumber());
            return healthRecordListVO;
        }).collect(Collectors.toList());
        pageVO.setContent(healthRecordListVOList);
        return pageVO;
    }

    @Override
    public HSSFWorkbook dowloadExecl() {
        List<HealthRecord> healthRecordList = healthRecordRepositiry.findAll();
        List<List<String>> values = new ArrayList<>();
        for (HealthRecord healthRecord : healthRecordList) {
            List<String> value = new ArrayList<>();
            WxUser wxUser = healthRecord.getWxUser();
            value.add(wxUser.getIsRegident() ? "住户" : "外来人员");
            value.add(wxUser.getName());
            value.add(wxUser.getGender());
            value.add(wxUser.getRoomNumber());
            value.add(String.valueOf(wxUser.getAccessNum()));
            value.add(String.valueOf(healthRecord.getTemperature()));
            value.add(String.valueOf(healthRecord.getTime()));
            values.add(value);
        }
        return ExeclUtil.getHSSFWorkbook(HealthRecordExecl.SHEETNAME
                , HealthRecordExecl.TITLES, values);
    }
}
